﻿//// 兼容C语言
//// test.cpp
//#include<stdio.h>
//int main()
//{
//	printf("hello world\n");
//	return 0;
//}

// test.cpp
// 这里的std cout看不懂，没关系，下面会依次讲解
//#include<iostream>
//using namespace std;
//
//int main()
//{
//	cout << "hello world\n" << endl;
//	return 0;
//}

//#include <stdio.h>
//#include <stdlib.h>
//int rand = 10;
//int main()
//{
//	// 编译报错：error C2365: “rand”: 重定义；以前的定义是“函数”
//	printf("%d\n", rand);
//	return 0;
//}


//#include <stdio.h>
//#include <stdlib.h>
//
//// 1. 正常的命名空间定义
//// Lzc是命名空间的名字，⼀般开发中是用项目名字做命名空间名
//// 日常练习可以用自己的名字命名
//namespace Lzc
//{
//	// 命名空间中可以定义变量/函数/类型
//	int rand = 10;
//	int Add(int left, int right)
//	{
//		return left + right;
//	}
//	struct Node
//	{
//		struct Node* next;
//		int val;
//	};
//}
//
//int main()
//{
//	printf("%p\n", rand);// 打印rand函数的地址
//	printf("%d\n", Lzc::rand);// 打印Lzc命名空间里的rand变量
//	return 0;
//}
//
////2. 命名空间可以嵌套
//namespace S
//{
//	namespace Lzc
//	{
//		int rand = 1;
//		int Add(int left, int right)
//		{
//			return left + right;
//		}
//	}
//
//	namespace Ysy
//	{
//		int rand = 2;
//		int Add(int left, int right)
//		{
//			return (left + right) * 10;
//		}
//	}
//}
//
//int main()
//{
//	printf("%d\n", S::Lzc::rand);// 1
//	printf("%d\n", S::Ysy::rand);// 2
//	printf("%d\n", S::Lzc::Add(1, 2));// 3
//	printf("%d\n", S::Ysy::Add(1, 2));// 30
//	return 0;
//}
//
////3. 多文件中可以定义同名namespace，他们会默认合并到⼀起，就像同一个namespace一样
//// Stack.h
//#pragma once
//#include<stdio.h>
//#include<stdlib.h>
//#include<stdbool.h>
//#include<assert.h>
//namespace Lzc
//{
//	typedef int STDataType;
//	typedef struct Stack
//	{
//		STDataType* a;
//		int top;
//		int capacity;
//	}ST;
//	void STInit(ST* ps, int n);
//	void STDestroy(ST* ps);
//	void STPush(ST* ps, STDataType x);
//	void STPop(ST* ps);
//	STDataType STTop(ST* ps);
//	int STSize(ST* ps);
//	bool STEmpty(ST* ps);
//}
//
//// Stack.cpp
//#include"Stack.h"
//namespace Lzc
//{
//	void STInit(ST* ps, int n)
//	{
//		assert(ps);
//		ps->a = (STDataType*)malloc(n * sizeof(STDataType));
//		ps->top = 0;
//		ps->capacity = n;
//	}
//	// 栈顶
//	void STPush(ST* ps, STDataType x)
//	{
//		assert(ps);
//		// 满了， 扩容
//		if (ps->top == ps->capacity)
//		{
//			printf("扩容\n");
//			int newcapacity = ps->capacity == 0 ? 4 : ps->capacity
//				* 2;
//			STDataType* tmp = (STDataType*)realloc(ps->a,
//				newcapacity * sizeof(STDataType));
//			if (tmp == NULL)
//			{
//				perror("realloc fail");
//				return;
//			}
//			ps->a = tmp;
//			ps->capacity = newcapacity;
//		}
//		ps->a[ps->top] = x;
//		ps->top++;
//	}
//	//...
//}
//
//// test.cpp
//#include"Stack.h"
//// 全局定义了一份单独的Stack
//typedef struct Stack
//{
//	int a[10];
//	int top;
//}ST;
//void STInit(ST* ps) {}
//void STPush(ST* ps, int x) {}
//
//int main()
//{
//	// 调用全局的
//	ST st1;
//	STInit(&st1);
//	STPush(&st1, 1);
//	STPush(&st1, 2);
//	printf("%d\n", sizeof(st1));
//	// 调用S namespace的
//	Lzc::ST st2;
//	printf("%d\n", sizeof(st2));
//	Lzc::STInit(&st2, 4);
//	Lzc::STPush(&st2, 1);
//	Lzc::STPush(&st2, 2);
//	return 0;
//}


//#include<stdio.h>
//
//namespace Lzc
//{
//	int a = 0;
//	int b = 1;
//}
//
//int main()
//{
//	// 编译报错：error C2065: “a”: 未声明的标识符
//	printf("%d\n", a);
//	return 0;
//}
//
////1. 指定命名空间访问
//int main()
//{
//	printf("%d\n", Lzc::a);
//	return 0;
//}
//
////2. using将命名空间中某个成员展开
//using Lzc::b;
//int main()
//{
//	printf("%d\n", Lzc::a);
//	printf("%d\n", b);
//	printf("%d\n", b);
//	printf("%d\n", b);
//	printf("%d\n", b);
//	printf("%d\n", b);
//	return 0;
//}
//
////3. 展开命名空间中全部成员
//using namespace Lzc;
//int main()
//{
//	printf("%d\n", a);
//	printf("%d\n", b);
//	return 0;
//}


//#define _CRT_SECURE_NO_WARNINGS 1
//#include <iostream>
//using namespace std;
//int main()
//{
//	int a = 0;
//	double b = 0.1;
//	char c = 'x';
//
//	cout << a << " " << b << " " << c << endl;
//	std::cout << a << " " << b << " " << c << std::endl;
//
//	scanf("%d%lf", &a, &b);
//	printf("%d %lf\n", a, b);
//
//	// 可以自动识别变量的类型
//	cin >> a;
//	cin >> b >> c;
//	cout << a << endl;
//	cout << b << " " << c << endl;
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//int main()
//{
//	// 在io需求⽐较⾼的地方，如部分大量输入的竞赛题中，加上以下3行代码
//	// 可以提高C++IO效率
//	ios_base::sync_with_stdio(false);
//	cin.tie(nullptr);
//	cout.tie(nullptr);
//	return 0;
//}


//#include <iostream>
//#include <assert.h>
//
//using namespace std;
//void Func(int a = 0)
//{
//	cout << a << endl;
//}
//
//int main()
//{
//	Func(); // 没有传参时，使用参数的默认值 0
//	Func(10); // 传参时，使用指定的实参 10
//	return 0;
//}

//#include <iostream>
//
//using namespace std;
//
//// 全缺省
//void Func1(int a = 10, int b = 20, int c = 30)
//{
//	cout << "a = " << a << endl;
//	cout << "b = " << b << endl;
//	cout << "c = " << c << endl << endl;
//}
//
//// 半缺省
//void Func2(int a, int b = 10, int c = 20)
//{
//	cout << "a = " << a << endl;
//	cout << "b = " << b << endl;
//	cout << "c = " << c << endl << endl;
//}
//
//int main()
//{
//	Func1();
//	Func1(1);
//	Func1(1, 2);
//	Func1(1, 2, 3);
//	Func2(100);
//	Func2(100, 200);
//	Func2(100, 200, 300);
//	return 0;
//}

//// Stack.h
//#include <iostream>
//#include <assert.h>
//
//using namespace std;
//
//typedef int STDataType;
//typedef struct Stack
//{
//	STDataType* a;
//	int top;
//	int capacity;
//}ST;
//
//void STInit(ST* ps, int n = 4);
//
//// Stack.cpp
//#include"Stack.h"
//
//// 缺省参数不能声明和定义同时给
//void STInit(ST* ps, int n)
//{
//	assert(ps && n > 0);
//	ps->a = (STDataType*)malloc(n * sizeof(STDataType));
//	ps->top = 0;
//	ps->capacity = n;
//}
//
//// test.cpp
//#include"Stack.h"
//
//int main()
//{
//	ST s1;
//	STInit(&s1);
//
//	// 确定要插入1000个数据，初始化时就开好，避免扩容
//	ST s2;
//	STInit(&s2, 1000);
//	return 0;
//}


//#include<iostream>
//
//using namespace std;
//
//// 1、参数类型不同
//int Add(int left, int right)
//{
//	cout << "int Add(int left, int right)" << endl;
//	return left + right;
//}
//
//double Add(double left, double right)
//{
//	cout << "double Add(double left, double right)" << endl;
//	return left + right;
//}
//
//// 2、参数个数不同
//void f()
//{
//	cout << "f()" << endl;
//}
//
//void f(int a)
//{
//	cout << "f(int a)" << endl;
//}
//
//// 3、参数类型顺序不同
//void f(int a, char b)
//{
//	cout << "f(int a,char b)" << endl;
//}
//
//void f(char b, int a)
//{
//	cout << "f(char b, int a)" << endl;
//}
//
//// 返回值不同不能作为重载条件，因为调用时也无法区分
////void fxx()
////{}
////
////int fxx()
////{
//// return 0;
////}
//
//// 下面两个函数构成重载
//// f1()调用时，会报错，存在歧义，编译器不知道调用谁
//void f1()
//{
//	cout << "f()" << endl;
//}
//
//void f1(int a = 10)
//{
//	cout << "f(int a)" << endl;
//}
//
//int main()
//{
//	Add(10, 20);
//	Add(10.1, 20.2);
//
//	f();
//	f(10);
//
//	f(10, 'a');
//	f('a', 10);
//
//	return 0;
//}


//#include<iostream>
//using namespace std;
//int main()
//{
//	int a = 0;
//	// 引用：b和c是a的别名
//	int& b = a;
//	int& c = a;
//	// 也可以给别名b取别名，d相当于还是a的别名
//	int& d = b;
//	++d;
//
//	// 这里取地址我们看到是⼀样的
//	cout << &a << endl;
//	cout << &b << endl;
//	cout << &c << endl;
//	cout << &d << endl;
//
//	return 0;
//}

//#include<iostream>
//
//using namespace std;
//
//int main()
//{
//	int a = 10;
//	// 编译报错：“ra”: 必须初始化引⽤
//	//int& ra;
//	int& b = a;
//	int c = 20;
//
//	// 这里并不是让b引用c，因为C++规定引用不能改变指向
//	// 这里是⼀个赋值，即 a = 20;
//	b = c;
//
//	cout << &a << endl;
//	cout << &b << endl;
//	cout << &c << endl;
//
//	return 0;
//}

//#include<iostream>
//
//using namespace std;
//
//void Swap(int& rx, int& ry)
//{
//	int tmp = rx;
//	rx = ry;
//	ry = tmp;
//}
//
//int main()
//{
//	int x = 0, y = 1;
//	cout << x << " " << y << endl;
//	Swap(x, y);
//	cout << x << " " << y << endl;
//	return 0;
//}

//#include<iostream>
//
//using namespace std;
//
//typedef int STDataType;
//typedef struct Stack
//{
//	STDataType* a;
//	int top;
//	int capacity;
//}ST;
//
//void STInit(ST& rs, int n = 4)
//{
//	rs.a = (STDataType*)malloc(n * sizeof(STDataType));
//	rs.top = 0;
//	rs.capacity = n;
//}
//
//// 栈顶
//void STPush(ST& rs, STDataType x)
//{
//	// 满了， 扩容
//	if (rs.top == rs.capacity)
//	{
//		printf("扩容\n");
//		int newcapacity = rs.capacity == 0 ? 4 : rs.capacity * 2;
//		STDataType* tmp = (STDataType*)realloc(rs.a, newcapacity *
//			sizeof(STDataType));
//		if (tmp == NULL)
//		{
//			perror("realloc fail");
//			return;
//		}
//		rs.a = tmp;
//		rs.capacity = newcapacity;
//	}
//	rs.a[rs.top] = x;
//	rs.top++;
//}
//
//// int STTop(ST& rs)
//int& STTop(ST& rs)
//{
//	return rs.a[rs.top - 1];
//}
//
//int main()
//{
//	ST st1;
//	STInit(st1);
//	STPush(st1, 1);
//	STPush(st1, 2);
//	cout << STTop(st1) << endl;// 2
//
//	STTop(st1) += 10;// 返回了rs.a[rs.top - 1]的别名，可以进行修改
//	cout << STTop(st1) << endl;// 12
//
//	return 0;
//}

//#include<iostream>
//#include<assert.h>
//
//using namespace std;
//typedef struct SeqList
//{
//	int a[10];
//	int size;
//}SLT;
//
//void SeqPushBack(SLT& sl, int x)
//{}
//
//typedef struct ListNode
//{
//	int val;
//	struct ListNode* next;
//}LTNode, * PNode;
//
//// 指针变量也可以取别名，这里LTNode*& phead就是给指针变量取别名
//// 这样就不需要用⼆级指针了，相对而言简化了程序
////void ListPushBack(LTNode** phead, int x)
////void ListPushBack(LTNode*& phead, int x)
//void ListPushBack(PNode& phead, int x)
//{
//	PNode newnode = (PNode)malloc(sizeof(LTNode));
//	assert(newnode);
//	newnode->val = x;
//	newnode->next = NULL;
//	if (phead == NULL)
//	{
//		phead = newnode;
//	}
//	else
//	{
//		//...
//	}
//}
//
//int main()
//{
//	PNode plist = NULL;
//	ListPushBack(plist, 1);
//
//	return 0;
//}

//int main()
//{
//	const int a = 10;
//
//	// 编译报错：error C2440: “初始化”: ⽆法从“const int”转换为“int &”
//	// 这里的引用是对a访问权限的放⼤
//	//int& ra = a;
//	
//	// 这样才可以
//	const int& ra = a;
//
//	// 编译报错：error C3892: “ra”: 不能给常量赋值
//	//ra++;
//	
//	// 这里的引用是对b访问权限的缩⼩
//	int b = 20;
//	const int& rb = b;
//
//	// 编译报错：error C3892: “rb”: 不能给常量赋值
//	//rb++;
//
//	return 0;
//}

//#include<iostream>
//
//using namespace std;
//
//int main()
//{
//	int a = 10;
//	const int& ra = 30;
//
//	// 编译报错: “初始化”: 无法从“int”转换为“int &”
//	// 临时对象具有常性
//	// int& rb = a * 3;
//
//	const int& rb = a * 3;
//	double d = 12.34;
//
//	// 编译报错：“初始化”: ⽆法从“double”转换为“int &”
//	// 临时对象具有常性
//	// int& rd = d;
//
//	const int& rd = d;
//
//	return 0;
//}


//#include<iostream>
//
//using namespace std;
//
//void f(int x)
//{
//	cout << "f(int x)" << endl;
//}
//
//void f(int* ptr)
//{
//	cout << "f(int* ptr)" << endl;
//}
//
//int main()
//{
//	f(0); // f(int x)
//	f(NULL); // f(int x)
//	f((int*)NULL); // 强制转换 f(int* ptr)
//
//	// 编译报错：error C2665: “f”: 2 个重载函数中没有一个匹配的参数类型
//	// f((void*)NULL);
//
//	f(nullptr); //f(int* ptr)
//	return 0;
//}


//#include<iostream>
//
//using namespace std;
//
//inline int Add(int x, int y)
//{
//	int ret = x + y;
//	ret += 1;
//	ret += 1;
//	ret += 1;
//	return ret;
//}
//int main()
//{
//	// 可以通过汇编观察程序是否展开
//	// 有call Add语句就是没有展开，没有就是展开了
//	int ret = Add(1, 2);
//	cout << Add(1, 2) * 5 << endl;
//	return 0;
//}

//// F.h
//#include <iostream>
//
//using namespace std;
//
//inline void f(int i);
//
//// F.cpp
//#include "F.h"
//
//void f(int i)
//{
//	cout << i << endl;
//}
//
//// main.cpp
//#include "F.h"
//
//int main()
//{
//	// 链接错误：无法解析的外部符号 "void __cdecl f(int)" (?f@@YAXH@Z)
//	f(10);
//	return 0;
//}

//#include <iostream>
//#include <assert.h>
//
//using namespace std;
//
//class Stack
//{
//public:
//	// 成员函数
//	void Init(int n = 4)
//	{
//		array = (int*)malloc(sizeof(int) * n);
//		if (nullptr == array)
//		{
//			perror("malloc申请空间失败");
//			return;
//		}
//		capacity = n;
//		top = 0;
//	}
//	void Push(int x)
//	{
//		// ...扩容
//		array[top++] = x;
//	}
//	int Top()
//	{
//		assert(top > 0);
//		return array[top - 1];
//	}
//	void Destroy()
//	{
//		free(array);
//		array = nullptr;
//		top = capacity = 0;
//	}
//private:
//	// 成员变量
//	int* array;
//	size_t capacity;
//	size_t top;
//}; // 分号不能省略
//
//int main()
//{
//	Stack st;
//	st.Init();
//	st.Push(1);
//	st.Push(2);
//	cout << st.Top() << endl;// 2
//	st.Destroy();
//	return 0;
//}
//
//class Date
//{
//public:
//	void Init(int year, int month, int day)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//private:
//	// 为了区分成员变量，⼀般习惯上成员变量
//	// 会加⼀个特殊标识，如 _开头 _结尾 或者 m_开头
//	int _year; // year_  m_year
//	int _month;
//	int _day;
//};
//
//int main()
//{
//	Date d;
//	d.Init(2024, 3, 31);
//
//	return 0;
//}
//
//
//// C++把struct升级成了类
//// 1、类里面可以定义函数
//// 2、struct名称就可以代表类型
//
//// C++兼容C中struct的用法
//typedef struct ListNodeC
//{
//	struct ListNodeC* next;
//	int val;
//}LTNode;
//
//// 不再需要typedef，ListNodeCPP就可以代表类型
//struct ListNodeCPP
//{
//	void Init(int x)
//	{
//		next = nullptr;
//		val = x;
//	}
//	ListNodeCPP* next;//
//	int val;
//};

//#include<iostream>
//
//using namespace std;
//
//class Stack
//{
//public:
//	// 成员函数
//	void Init(int n = 4);
//private:
//	// 成员变量
//	int* array;
//	size_t capacity;
//	size_t top;
//};
//
//// 声明和定义分离，需要指定类域
//void Stack::Init(int n)
//{
//	array = (int*)malloc(sizeof(int) * n);
//	if (nullptr == array)
//	{
//		perror("malloc申请空间失败");
//		return;
//	}
//	capacity = n;
//	top = 0;
//}
//
//int main()
//{
//	Stack st;
//	st.Init();
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class Date
//{
//public:
//	void Init(int year, int month, int day)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//	void Print()
//	{
//		cout << _year << "/" << _month << "/" << _day << endl;
//	}
//private:
//	// 这里只是声明，没有开空间
//	int _year;
//	int _month;
//	int _day;
//};
//int main()
//{
//	// Date类实例化出对象d1和d2
//	Date d1;
//	Date d2;
//
//	d1.Init(2024, 3, 31);
//	d1.Print();
//
//	d2.Init(2024, 7, 5);
//	d2.Print();
//
//	return 0;
//}

//#include <iostream>
//
//using namespace std;
//
//class B
//{
//public:
//	void Print()
//	{
//		//...
//	}
//};
//class C
//{};
//int main()
//{
//	B b;
//	C c;
//	cout << sizeof(b) << endl;
//	cout << sizeof(c) << endl;
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class Date
//{
//public:
//	// void Init(Date* const this, int year, int month, int day)
//	void Init(int year, int month, int day)
//	{
//		// 编译报错：error C2106 : “ = ” :左操作数必须为左值
//		// this = nullptr;
//		// this->_year = year;
//		_year = year;
//		this->_month = month;
//		this->_day = day;
//	}
//	void Print()
//	{
//		cout << _year << "/" << _month << "/" << _day << endl;
//	}
//private:
//	// 这里只是声明，没有开空间
//	int _year;
//	int _month;
//	int _day;
//};
//int main()
//{
//	// Date类实例化出对象d1和d2
//	Date d1;
//	Date d2;
//
//	// d1.Init(&d1, 2024, 3, 31);// 实际上
//	d1.Init(2024, 3, 31);
//	d1.Print();
//
//	d2.Init(2024, 7, 5);
//	d2.Print();
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class A
//{
//public:
//	void Print()
//	{
//		cout << "A::Print()" << endl;
//	}
//private:
//	int _a;
//};
//
//int main()
//{
//	A* p = nullptr;// 拿到一个A类型对象的地址
//	p->Print();// 因为函数不在对象里，所以正常运行
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class A
//{
//public:
//	void Print()
//	{
//		cout << "A::Print()" << endl;
//		cout << _a << endl;
//	}
//private:
//	int _a;
//};z
//
//int main()
//{
//	A* p = nullptr;
//	p->Print();
//
//	return 0;
//}
//#include<iostream>
//using namespace std;
//class Date
//{
//public:
//	// 1.无参构造函数
//	Date()
//	{
//		_year = 1;
//		_month = 1;
//		_day = 1;
//	}
//
//	// 2.带参构造函数
//	Date(int year, int month, int day)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//
//	// 3.全缺省构造函数
//		/*Date(int year = 1, int month = 1, int day = 1)
//		 {
//		 _year = year;
//		 _month = month;
//		 _day = day;
//		 }*/
//	void Print()
//	{
//		cout << _year << "/" << _month << "/" << _day << endl;
//	}
//private:
//	int _year;
//	int _month;
//	int _day;
//};
//
//int main()
//{
//	// 如果留下三个构造中的第⼆个带参构造，第⼀个和第三个注释掉
//	// 编译报错：error C2512 : “Date”:没有合适的默认构造函数可用
//
//	Date d1;// 调用默认构造函数
//
//	Date d2(2025, 1, 1); // 调用带参的构造函数
//
//	// 注意：如果通过无参构造函数创建对象时，对象后面不用跟括号，否则编译器无法
//	// 区分这里是函数声明还是实例化对象
//	// warning C4930: “Date d3(void)”: 未调用原型函数(是否是有意用变量定义的? )
//	Date d3();
//
//	d1.Print();
//	d2.Print();
//	return 0;
//}
//
//#include<iostream>
//using namespace std;
//typedef int STDataType;
//class Stack
//{
//public:
//	Stack(int n = 4)
//	{
//		_a = (STDataType*)malloc(sizeof(STDataType) * n);
//		if (nullptr == _a)
//		{
//			perror("malloc申请空间失败");
//			return;
//		}
//		_capacity = n;
//		_top = 0;
//	}
//	// ...
//private:
//	STDataType* _a;
//	size_t _capacity;
//	size_t _top;
//};
//
//// 两个Stack实现队列
//class MyQueue
//{
//public:
//	// 编译器默认生成MyQueue的构造函数调用了Stack的构造函数，完成了两个成员的初始化
//
//private:
//	Stack pushst;
//	Stack popst;
//};
//
//int main()
//{
//	MyQueue mq;
//	return 0;
//}

//#include<iostream>
//using namespace std;
//typedef int STDataType;
//class Stack
//{
//public:
//	Stack(int n = 4)
//	{
//		_a = (STDataType*)malloc(sizeof(STDataType) * n);
//		if (nullptr == _a)
//		{
//			perror("malloc申请空间失败");
//				return;
//		}
//		_capacity = n;
//		_top = 0;
//	}
//
//	~Stack()
//	{
//		cout << "~Stack()" << endl;
//		free(_a);
//		_a = nullptr;
//		_top = _capacity = 0;
//	}
//private:
//	STDataType* _a;
//	size_t _capacity;
//	size_t _top;
//};
//
//// 两个Stack实现队列
//class MyQueue
//{
//public:
//	// 编译器默认生成MyQueue的析构函数调用了Stack的析构，释放的Stack内部的资源
//	// 显示写析构，也会自动调用Stack的析构
//	/*~MyQueue()
//	{}*/
//private:
//	Stack pushst;
//	Stack popst;
//};
//
//int main()
//{
//	Stack st;
//	MyQueue mq;
//
//	return 0;
//}
//
//#include<iostream>
//using namespace std;
//
//class S
//{
//public:
//	S()
//	{
//
//	}
//	S(S b)
//	{
//		cout << "b" << endl;
//	}
//};
//
//int main()
//{
//	S s;
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class Date
//{
//public:
//	Date(int year = 1, int month = 1, int day = 1)// 默认构造函数
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//
//	// 编译报错：error C2652 : “Date”:非法的复制构造函数:第一个参数不应是“Date”
//	//Date(Date d)
//	Date(const Date& d)// 拷贝构造函数
//	{
//		_year = d._year;
//		_month = d._month;
//		_day = d._day;
//	}
//
//	Date(Date* d)// 带参的构造函数，虽然能完成拷贝，但不是拷贝构造函数
//	{
//		_year = d->_year;
//		_month = d->_month;
//		_day = d->_day;
//	}
//
//	void Print()
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//
//private:
//	int _year;
//	int _month;
//	int _day;
//};
//
//void Func1(Date d)
//{
//	cout << &d << endl;
//	d.Print();
//}
//
//// Date Func2()
//Date& Func2()
//{
//	Date tmp(2024, 7, 5);
//	tmp.Print();
//	return tmp;
//}
//
//int main()
//{
//	Date d1(2024, 7, 5);
//
//	// C++规定自定义类型对象进行传值行为(传值传参，传值返回)必须调用拷贝构造，所以这里传值传参要调用拷贝构造
//    // 所以这里的d1传值传参给d要调用拷贝构造函数完成拷贝，引用传参可以减少这里的拷贝
//    Func1(d1);
//	cout << &d1 << endl;
//
//	// 这里可以完成拷贝，但是调用的不是拷贝构造函数，而是一个带参的构造函数
//	Date d2(&d1);
//	d1.Print();
//	d2.Print();
//
//	//这样写调用的才是拷贝构造函数，通过同类型的对象初始化，而不是指针
//    Date d3(d1);
//	d2.Print();
//
//	// 也可以这样写，这里调用的也是拷贝构造函数
//	Date d4 = d1;// 用的较多
//	d2.Print();
//
//	// Func2返回了一个局部对象tmp的引用作为返回值
//	// Func2函数结束，tmp对象就销毁了，相当于了一个野引用
//	Date ret = Func2();
//	ret.Print();
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//typedef int STDataType;
//class Stack
//{
//public:
//    Stack(int n = 4)// 默认构造函数
//    {
//        _a = (STDataType*)malloc(sizeof(STDataType) * n);
//        if (nullptr == _a)
//        {
//            perror("malloc申请空间失败");
//            return;
//        }
//        _capacity = n;
//        _top = 0;
//    }
//
//    Stack(const Stack& st)// 拷贝构造函数
//    {
//        // 需要对 _a指向资源创建同样大的资源再拷贝值，即深拷贝
//        _a = (STDataType*)malloc(sizeof(STDataType) * st._capacity);
//        if (nullptr == _a)
//        {
//            perror("malloc申请空间失败!!!");
//            return;
//        }
//        memcpy(_a, st._a, sizeof(STDataType) * st._top);
//        _top = st._top;
//        _capacity = st._capacity;
//    }
//
//    void Push(STDataType x)
//    {
//        if (_top == _capacity)
//        {
//            int newcapacity = _capacity * 2;
//            STDataType* tmp = (STDataType*)realloc(_a, newcapacity *
//                sizeof(STDataType));
//            if (tmp == NULL)
//            {
//                perror("realloc fail");
//                return;
//            }
//            _a = tmp;
//            _capacity = newcapacity;
//        }
//        _a[_top++] = x;
//    }
//
//    ~Stack()// 析构函数
//    {
//        cout << "~Stack()" << endl;
//        free(_a);
//        _a = nullptr;
//        _top = _capacity = 0;
//    }
//
//private:
//    STDataType* _a;
//    size_t _capacity;
//    size_t _top;
//};
//
//// 两个Stack实现队列
//class MyQueue
//{
//public:
//private:
//    Stack pushst;
//    Stack popst;
//};
//
//int main()
//{
//    Stack st1;
//    st1.Push(1);
//    st1.Push(2);
//    // Stack不显示实现拷贝构造，用自动生成的拷贝构造完成浅拷贝
//    // 会导致st1和st2里面的_a指针指向同一块资源，并且会析构两次，程序崩溃
//    Stack st2 = st1;
//
//    MyQueue mq1;
//    // MyQueue自动生成的拷贝构造，会自动调用Stack拷贝构造完成pushst / popst
//    // 的拷贝，只要Stack拷贝构造自己实现了深拷贝，他就没问题
//    MyQueue mq2 = mq1;
//
//    return 0;
//}


//#include<iostream>
//using namespace std;
//
//// 编译报错：“operator + ”必须至少有一个类类型的形参
//int operator+(int x, int y)
//{
//	return x - y;
//}
//
//class A
//{
//public:
//	void func()
//	{
//		cout << "A::func()" << endl;
//	}
//};
//typedef void(A::* PF)(); //成员函数指针类型
//// 本来是typedef void(*)() PF; 但函数指针和数组指针typedef的别名，要写在()里面
//// 然后是成员函数，就加个A::
//// 此时 PF = void(A::*)()
//
//int main()
//{
//	// C++规定成员函数要加&才能取到函数指针
//	PF pf = &(A::func);
//
//	A obj;
//	// obj对象调用成员函数指针时，使用.*运算符
//	(obj.*pf)();
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//class Date
//{
//public:
//	Date(int year = 1, int month = 1, int day = 1)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//
//	void Print()
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//	//private:
//	int _year;
//	int _month;
//	int _day;
//};
//
//// 重载为全局函数时访问对象私有成员变量存在问题
//// 有几种方法可以解决：
//// 1、成员放公有
//// 2、Date提供getxxx函数
//// 3、友元函数，C++初阶——类和对象(下)
//// 4、重载为成员函数，但参数会少一个，因为第一个运算对象传给了隐藏的this指针
//
//bool operator==(const Date& d1, const Date& d2)
//{
//	return d1._year == d2._year
//		&& d1._month == d2._month
//		&& d1._day == d2._day;
//}
//int main()
//{
//	Date d1(2024, 7, 5);
//	Date d2(2024, 7, 6);
//
//	// 运算符重载函数可以显示调用
//	operator==(d1, d2);
//
//	d1 == d2;// 编译器会转换成operator==(d1, d2);
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//class Date
//{
//public:
//    Date(int year = 1, int month = 1, int day = 1)
//    {
//        _year = year;
//        _month = month;
//        _day = day;
//    }
//
//    void Print()
//    {
//        cout << _year << "-" << _month << "-" << _day << endl;
//    }
//
//    bool operator==(const Date& d)
//    {
//        return _year == d._year
//            && _month == d._month
//            && _day == d._day;
//    }
//
//    Date& operator++()
//    {
//        cout << "前置++" << endl;
//        //...
//        return *this;
//    }
//
//    Date operator++(int)//也可以写成Date operator++(int i)，但不会使用i
//    {
//        Date tmp;
//        cout << "后置++" << endl;
//        //...
//        return tmp;
//    }
//
//private:
//    int _year;
//    int _month;
//    int _day;
//};
//int main()
//{
//    Date d1(2024, 7, 5);
//    Date d2(2024, 7, 6);
//
//    // 运算符重载函数可以显⽰调用
//    d1.operator==(d2);
//    
//    d1 == d2;// 编译器会转换成d1.operator==(d2);
//    
//    ++d1;// 编译器会转换成d1.operator++();
//    
//    d1++;// 编译器会转换成d1.operator++(0);()里随便一个整数
//
//    return 0;
//}

//#include<iostream>
//using namespace std;
//
//class Date
//{
//public:
//	Date(int year = 1, int month = 1, int day = 1)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//
//	Date(const Date& d)
//	{
//		cout << " Date(const Date& d)" << endl;
//		_year = d._year;
//		_month = d._month;
//		_day = d._day;
//	}
//	
//	// 传引用返回减少拷贝
//	// d1 = d2;
//	Date& operator=(const Date& d)
//	{
//		// 不要检查自己给自己赋值的情况
//		if (this != &d)
//		{
//			_year = d._year;
//			_month = d._month;
//			_day = d._day;
//		}
//
//		// d1 = d2表达式的返回对象应该为d1，也就是* this
//		return *this;
//	}
//
//	void Print()
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//
//private:
//	int _year;
//	int _month;
//	int _day;
//};
//int main()
//{
//	Date d1(2024, 7, 5);
//	Date d2(d1);
//	Date d3(2024, 7, 6);
//
//	d1 = d3;
//
//	// 需要注意这里是拷贝构造，不是赋值重载
//	// 请牢牢记住赋值重载完成两个已经存在的对象直接的拷贝赋值
//	// 而拷贝构造函数用于一个已经存在的对象初始化给另一个要创建的对象
//	Date d4 = d1;
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//class Date
//{
//public:
//	Date(int year = 1, int month = 1, int day = 1)
//	{
//		_year = year;
//		_month = month;
//		_day = day;
//	}
//
//	// void Print(const Date* const this) const
//	void Print() const
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//
//private:
//	int _year;
//	int _month;
//	int _day;
//};
//
//int main()
//{
//	// 这里非const对象也可以调用const成员函数是一种权限的缩小
//    Date d1(2024, 7, 5);
//	d1.Print();
//
//	const Date d2(2024, 8, 5);
//	d2.Print();
//
//	return 0;
//}

//class Date
//{
//public:
//	Date* operator&()
//	{
//		return this;
//		// return nullptr;
//	}
//	const Date* operator&()const
//	{
//		return this;
//		// return nullptr;
//	}
//
//private:
//	int _year; // 年
//	int _month; // 月
//	int _day; // 日
//};

//#include<iostream>
//using namespace std;
//
//class Time
//{
//public:
//	Time(int hour)
//		:_hour(hour)
//	{
//		cout << "Time()" << endl;
//	}
//private:
//	int _hour;
//};
//
//class Date
//{
//public:
//	Date(int& x, int year = 1, int month = 1, int day = 1)
//		:_year(year)
//		, _month(month)
//		, _day(day)
//		//, _t(12)
//		//, _ref(x)
//		//, _n(1)
//	{
//		// error C2512: “Time”: 没有合适的默认构造函数可用
//		// error C2530 : “Date::_ref” : 必须初始化引用
//		// error C2789 : “Date::_n” : 必须初始化常量限定类型的对象
//	}
//	void Print() const
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//private:
//	int _year;
//	int _month;
//	int _day;
//	Time _t;       // 没有默认构造的类类型成员变量
//	int& _ref;          // 引用成员变量
//	const int _n;   // const成员变量
//};
//
//int main()
//{
//	int i = 0;
//	Date d1(i);
//	d1.Print();
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//class Time
//{
//public:
//	Time(int hour)
//		:_hour(hour)
//	{
//		cout << "Time()" << endl;
//	}
//private:
//	int _hour;
//};
//
//class Date
//{
//public:
//	Date()
//		:_month(2)
//	{
//		cout << "Date()" << endl;
//	}
//	void Print() const
//	{
//		cout << _year << "-" << _month << "-" << _day << endl;
//	}
//private:
//	// 注意这里不是初始化，这里给的是缺省值，这个缺省值是给初始化列表用的
//	// 如果初始化列表没有显示初始化，默认就会用这个缺省值初始化
//
//	int _year = 1;
//	int _month = 1;
//	int _day;
//	Time _t = 1;
//	const int _n = 1;
//	int* _ptr = (int*)malloc(12);
//};
//int main()
//{
//	Date d1;
//	d1.Print();
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//class A
//{
//public:
//	A(int a)
//		:_a1(a)
//		,_a2(_a1)
//	{
//	}
//	void Print() {
//		cout << _a1 << " " << _a2 << endl;
//	}
//private:
//	int _a2 = 2;
//	int _a1 = 2;
//};
//
//int main()
//{
//	A aa(1);
//	aa.Print();
//}

//#include<iostream>
//using namespace std;
//
//class A
//{
//public:
//	// explicit构造函数，就不再支持隐式类型转换
//	// explicit A(int a1)
//    A(int a1)
//        :_a1(a1)
//    { }
//
//	//explicit A(int a1, int a2)
//	A(int a1, int a2)
//		:_a1(a1)
//		, _a2(a2)
//    { }
//
//	void Print()
//	{
//		cout << _a1 << " " << _a2 << endl;
//	}
//
//    int Get() const
//    {
//        return _a1 + _a2;
//    }
//private:
//    int _a1 = 1;
//    int _a2 = 2;
//};
//
//class B
//{
//public:
//    B(const A& a)
//        :_b(a.Get())
//    { }
//private:
//    int _b = 0;
//};
//int main()
//{
//    // 1构造一个A的临时对象，再用这个临时对象拷贝构造aa1
//    // 编译器遇到连续构造+拷贝构造->优化为直接构造
//    A aa1 = 1;
//    aa1.Print();
//
//    // aa2是临时对象的别名，此时临时对象的生命周期也随之改变
//    const A& aa2 = 1;
//
//    // C++11之后才支持多参数转化
//    A aa3 = { 2,2 };
//
//    // aa3隐式类型转换为b对象
//    // 原理跟上面类似
//    B b = aa3;
//    const B& rb = aa3;
//
//    return 0;
//}

//#include<iostream>
//using namespace std;
//
//class A
//{
//public:
//	void func()
//	{
//		cout << "Hello World!" << endl;
//	}
//private:
//	static int i;
//};
//
//int A::i = 1;
//
//
//int main()
//{
//	//cout << A::i << endl;
//	return 0;
//}

//// 实现⼀个类，计算程序中创建出了多少个类对象？
//#include<iostream>
//using namespace std;
//class A
//{
//public:
//	A()
//	{
//		++_scount;
//	}
//	A(const A& t)
//	{
//		++_scount;
//	}
//	~A()
//	{
//		--_scount;
//	}
//	static int GetACount()
//	{
//		return _scount;
//	}
//private:
//	// 类里面声明
//	static int _scount;
//};
//// 类外面初始化
//int A::_scount = 0;
//
//int main()
//{
//	cout << A::GetACount() << endl; // 0
//	A a1, a2;
//	A a3(a1);
//	cout << A::GetACount() << endl; // 3
//	cout << a1.GetACount() << endl; // 3
//	// 编译报错：error C2248 : “A::_scount” :无法访问private成员(在“A”类中声明)
//	//cout << A::_scount << endl;
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//// 前置声明，否则A的友元函数声明编译器不认识B
//class B;
//
//class A
//{
//	// 友元声明
//	friend void func(const A& aa, const B& bb);
//private:
//	int _a1 = 1;
//};
//
//class B
//{
//	// 友元声明
//	friend void func(const A& aa, const B& bb);
//private:
//	int _b1 = 3;
//};
//
//void func(const A& aa, const B& bb)
//{
//	cout << aa._a1 << endl; //  1
//	cout << bb._b1 << endl; //  3
//}
//
//int main()
//{
//	A aa;
//	B bb;
//	func(aa, bb);
//
//	return 0;
//}

//#include<iostream>
//using namespace std;
//
//class A
//{
//	// 友元声明
//	friend class B;
//private:
//	void F() const
//	{
//		cout << "F" << endl;
//	}
//	int _a1 = 1;
//};
//
//class B
//{
//public:
//	void func1(const A& aa)
//	{
//		cout << aa._a1 << endl; // 1
//		aa.F(); // F
//		cout << _b1 << endl; // 3
//	}
//private:
//	int _b1 = 3;
//};
//
//int main()
//{
//	A aa;
//	B bb;
//	bb.func1(aa);
//
//	return 0;
//}

//#include<iostream>
//using namespace std;

//class A
//{
//public:
//    class B // B默认就是A的友元
//    {
//    public:
//        void foo(const A& a)
//        {
//            cout << _k << endl;          // 1 OK
//            cout << a._h << endl;        // 1 OK
//        }
//    private:
//        int _b = 1;
//    };
//private:
//    static int _k;
//    int _h = 1;
//};
//
//int A::_k = 1;
//
//int main()
//{
//    // sizeof是当创建这个类型的一个对象（或变量）的时候，需要为它分配的空间的大小
//    // sizeof会忽略static成员变量的大小
//    cout << sizeof(A) << endl; // 4,
//    A::B b;
//    A aa;
//
//    b.foo(aa);
//
//    return 0;
//}

//#include<iostream>
//using namespace std;
//
//class A
//{
//public:
//    A(int a = 0)
//        :_a(a)
//    {
//        cout << "A(int a)" << endl;
//    }
//    ~A()
//    {
//        cout << "~A()" << endl;
//    }
//private:
//    int _a;
//};
//
//class Solution {
//public:
//    int Sum_Solution(int n) {
//        //...
//        return n;
//    }
//};
//
//int main()
//{
//    A aa1;
//    // 不能这么定义对象，因为编译器无法识别是⼀个函数声明，还是对象定义
//    //A aa1();
//    
//    // 但是我们可以这么定义匿名对象，匿名对象的特点不用取名字，
//    // 但是他的生命周期只有这一行，我们可以看到下一行他就会自动调用析构函数
//    A();
//    A(1);
//
//    A aa2(2);
//
//    // 匿名对象在这样场景下就很好用，当然还有一些其他使用场景，这个我们以后遇到了再说
//    // 匿名对象Solution()
//    Solution().Sum_Solution(10);
//
//    return 0;
//}


// 一年中的第几天
//#include <iostream>
//using namespace std;
//
//int sumDay(int year, int month, int day)
//{
//    int month_day[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };
//    int sumDay = 0;
//    for (int i = 1; i < month; ++i)
//    {
//        if (i == 2 && (year % 400 == 0 || year % 4 == 0 && year % 100 != 0))
//        {
//            sumDay += 29;
//            continue;
//        }
//        sumDay += month_day[i];
//    }
//    return sumDay + day;
//}
//
//int main() {
//    int year, month, day;
//    cin >> year >> month >> day;
//    cout << sumDay(year, month, day) << endl;
//    return 0;
//}


// 日期-日期 2-1 = 2
//#include <iostream>
//using namespace std;
//
//class Date
//{
//public:
//    Date(int year, int month, int day)
//        :_year(year)
//        , _month(month)
//        , _day(day)
//    {
//    }
//
//    int sumDay() const
//    {
//        int month_day[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };
//        int sumDay = 0;
//        for (int i = 1; i < _month; ++i)
//        {
//            if (i == 2 && (_year % 400 == 0 || _year % 4 == 0 && _year % 100 != 0))
//            {
//                sumDay += 29;
//                continue;
//            }
//            sumDay += month_day[i];
//        }
//        return sumDay + _day;
//    }
//
//    int operator-(const Date & d)
//    {
//        int day1 = sumDay() - d.sumDay();
//        int day2 = 0;
//        for (int i = _year; i < d._year; ++i)
//        {
//            if(i % 400 == 0 || i % 4 == 0 && i % 100 != 0)
//            ++day2;
//        }
//        return day1 + (_year - d._year) * 365 + day2;
//    }
//
//private:
//    int _year;
//    int _month;
//    int _day;
//};
//
//int day(int date1, int date2)
//{
//    int max = date1;
//    int min = date2;
//    if (max < min)
//    {
//        max = date2;
//        min = date1;
//    }
//    Date d1(max / 10000, max / 100 % 100, max % 100);
//    Date d2(min / 10000, min / 100 % 100, min % 100);
//    return (d1 - d2) + 1;
//}
//int main() {
//    int date1, date2;
//    cin >> date1 >> date2;
//    cout << day(date1, date2) << endl;
//}

// 一个日期加上若干天后是什么日期
//#include <iostream>
//#include <assert.h>
//using namespace std;
//
//class Date
//{
//public:
//    Date(int year, int month, int day)
//        :_year(year)
//        , _month(month)
//        , _day(day)
//    {
//    }
//    int monthDay()
//    {
//        assert(_month > 0 && _month < 13);
//        int month_day[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };
//        if (_month == 2 && (_year % 400 == 0 || _year % 100 != 0 && _year % 4 == 0))
//            return 29;
//        return month_day[_month];
//    }
//    Date& operator+=(int addDay)
//    {
//        _day += addDay;
//        while (_day > monthDay())
//        {
//            _day -= monthDay();
//            ++_month;
//            if (_month > 12)
//            {
//                ++_year;
//                _month = 1;
//            }
//        }
//        return *this;
//    }
//    void print()
//    {
//        printf("%d-%02d-%02d\n", _year, _month, _day);
//    }
//private:
//    int _year;
//    int _month;
//    int _day;
//};
//
//void addDate()
//{
//    int year, month, day;
//    int addDay;
//    cin >> year >> month >> day >> addDay;
//    Date d(year, month, day);
//    d += addDay;
//    d.print();
//}
//
//int main() {
//    int m;
//    cin >> m;
//    while (m--)
//    {
//        addDate();
//    }
//}

// 给出年分m和一年中的第n天，算出第n天是几月几号
//#include <iostream>
//using namespace std;
//
//class Date
//{
//public:
//    Date(int year, int month = 1, int day = 1)
//        :_year(year)
//        , _month(month)
//        , _day(day)
//    {
//    }
//    int monthDay()
//    {
//        int month_day[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };
//        if (_month == 2 && (_year % 400 == 0 || _year % 100 != 0 && _year % 4 == 0))
//            return 29;
//        return month_day[_month];
//    }
//    Date& operator+=(int sumDay)
//    {
//        _day = sumDay;
//        while (_day > monthDay())
//        {
//            _day -= monthDay();
//            ++_month;
//        }
//        return *this;
//    }
//    void print()
//    {
//        printf("%d-%02d-%02d\n", _year, _month, _day);
//    }
//private:
//    int _year;
//    int _month;
//    int _day;
//};
//
//int main() {
//    int year, sumDay;
//    while (scanf("%d%d", &year, &sumDay) != EOF) // while(cin>>year>>sumDay) 也行
//    {
//        Date d(year);
//        d += sumDay;
//        d.print();
//    }
//}

//void Test()
//{
//	// 动态申请一个int类型的空间
//	int* ptr1 = new int;
//	// 动态申请一个int类型的空间并初始化为10
//	int* ptr2 = new int(10);
//	// 动态申请10个int类型的空间
//	int* ptr3 = new int[10];
//	// 动态申请10个int类型的空间并初始化为0
//	int* ptr4 = new int[10] {0};
//	// 动态申请10个int类型的空间
//	// 前5个初始化为1,2,3,4,5，后5个初始化为0
//	int* ptr5 = new int[10]{1,2,3,4,5};
//
//	delete ptr1;
//	delete ptr2;
//	delete[] ptr3;
//	delete[] ptr4;
//	delete[] ptr5;
//}
//
//int main()
//{
//	Test();
//	return 0;
//}

//#include <iostream>
//using namespace std;
//
//class A
//{
//public:
//	A(int a = 0)
//		: _a(a)
//	{
//		cout << "A():" << this << endl;
//	}
//	~A()
//	{
//		cout << "~A():" << this << endl;
//	}
//
//private:
//	int _a = 1;
//};
//int main()
//{
//	// new/delete 和 malloc/free最大区别是 new/delete对于【自定义类型】除了开空间
//	//还会调用构造函数和析构函数
//	A* p1 = (A*)malloc(sizeof(A));
//	A* p2 = new A(1);
//	free(p1);
//	delete p2;
//
//	// 内置类型是几乎是一样的
//	int* p3 = (int*)malloc(sizeof(int)); // C
//	int* p4 = new int;
//	free(p3);
//	delete p4;
//
//	A* p5 = (A*)malloc(sizeof(A) * 10);
//	A* p6 = new A[10];
//	free(p5);
//	delete[] p6;
//
//	return 0;
//}

//#include <iostream>
//using namespace std;
//
//class A
//{
//public:
//	A(int a = 0)
//		: _a(a)
//	{
//		cout << "A():" << this << endl;
//	}
//	~A()
//	{
//		cout << "~A():" << this << endl;
//	}
//private:
//	int _a;
//};
//
//// 定位new/replacement new
//int main()
//{
//	// p1现在指向的只不过是与A对象相同大小的一段空间，还不能算是一个对象，因为没有调用构造函数
//	A* p1 = (A*)malloc(sizeof(A));
//	new(p1)A;  // 注意：如果A类的构造函数有参数时，此处需要传参
//	p1->~A();  // 析构可以直接显示调用，显示调用构造函数要通过定位new表达式
//	free(p1);
//
//	A* p2 = (A*)operator new(sizeof(A));
//	new(p2)A(10);
//	p2->~A();
//	operator delete(p2);
//
//	return 0;
//}

//void Swap(int& left, int& right)
//{
//	int temp = left;
//	left = right;
//	right = temp;
//}
//void Swap(double& left, double& right)
//{
//	double temp = left;
//	left = right;
//	right = temp;
//}
//void Swap(char& left, char& right)
//{
//	char temp = left;
//	left = right;
//	right = temp;
//}
////……


//template<typename T>
//void Swap(T& left, T& right)
//{
//	T temp = left;
//	left = right;
//	right = temp;
//}


//template<class T>
//T Add(const T& left, const T& right)
//{
//	return left + right;
//}
//
//int main()
//{
//	int a1 = 10, a2 = 20;
//	double d1 = 10.0, d2 = 20.0;
//
//	// 隐式实例化
//	Add(a1, a2);
//	Add(d1, d2);
//	/*
//	   该语句不能通过编译，因为在编译期间，当编译器看到该实例化时，需要推演其实参类型,
//	   通过实参a1将T推演为int，通过实参d1将T推演为double类型，但模板参数列表中只有
//	   一个T，编译器无法确定此处到底该将T确定为int 或者 double类型而报错。
//	   注意：在模板中，编译器一般不会进行类型转换，因为一旦转化出问题，编译器就需要背黑锅
//	Add(a1, d1);
//	 */
//
//	// 此时有两种处理方式: 1. 用户自己来类型转换  2. 使用显式实例化
//	Add(a1, (int)d1);
//
//	// 显式实例化
//	Add<int>(a1, d1);
//
//	return 0;
//}


//// 专门处理int的加法函数
//int Add(int left, int right)
//{
//	return left + right;
//}
//
//// 通用加法函数
//template<class T>
//T Add(T left, T right)
//{
//	return left + right;
//}
//
//void Test()
//{
//	Add(1, 2);
//	Add<int>(1, 2);
//}


//// 专门处理int的加法函数
//int Add(int left, int right)
//{
//	return left + right;
//}
//
//// 通用加法函数
//template<class T1, class T2>
//T1 Add(T1 left, T2 right)
//{
//	return left + right;
//}
//
//void Test()
//{
//	Add(1, 2); // 与非模板函数类型完全匹配，不需要函数模板实例化
//
//	Add(1, 2.0); // 函数模板可以生成更好匹配的版本，编译器根据实参生成更好匹配的Add函数
//}


//template<class T1, class T2, ..., class Tn>
//class 类模板名
//{
//	// 类内成员定义
//};


//#include<iostream>
//using namespace std;
//
// 类模版
//template<typename T>
//class Stack
//{
//public:
//	Stack(size_t capacity = 4)
//		:_aaray(new new T[capacity])
//		,_capacity(capacity)
//		,_size(0)
//	{}
//
//	void Push(const T& data);
//
//private:
//	T* _array;
//	size_t _capacity;
//	size_t _size;
//};
//
//// 类模版的成员函数，不建议声明和定义分离到两个文件.h 和.cpp会出现链接错误
//// 在同一个文件中声明和定义分离，
//// 要在函数上方再写个模板参数template<class T>，和指定类域Stack<T>::
//template<class T>
//void Stack<T>::Push(const T& data)
//{
//	// 扩容
//	_array[_size] = data;
//	++_size;
//}
//
//int main()
//{
//	Stack<int> st1;    // int
//	Stack<double> st2; // double
//	return 0;
//}


//int main()
//{
//	// 类模板都是显示实例化
//	Stack<int> st1; // int
//	st1.Push(1);
//	st1.Push(2);
//	st1.Push(3);
//
//	Stack<double> st2; // double
//	st2.Push(1.1);
//	st2.Push(1.1);
//	st2.Push(1.1);
//
//	// 同时有int、double类型的两个栈，而typedef就达不到这样的效果
//
//	return 0;
//}


//#include <iostream>
//#include <string>
//#include <vector>
//
//using namespace std;
//
//int main()
//{
//	vector<string> v;
//	v.push_back("aaa");
//	for (auto e : v)
//	{
//		e[0] += 2;
//		cout << e;
//	}
//	cout << endl;
//	cout << v[0] << endl;
//	return 0;
//}

//#include <string>
//#include <algorithm>
//using namespace std;
//
//string addStrings(string num1, string num2) {
//    int size1 = num1.size(), size2 = num2.size();
//    string s1;
//    s1.reserve(size1 > size2 ? size1 + 1 : size2 + 1);
//    int i = num1.size()-1, j = num2.size()-1;
//    int x = 0; // 进位
//    while (i >= 0  || j >= 0)
//    {
//        int m = i >= 0 ? num1[i]-'0' : 0;
//        int n = j >= 0 ? num2[j]-'0' : 0;
//        if (m + n + x >= 10)
//        {
//            s1 += m + n + x - 10 + '0';
//            x = 1;
//        }
//        else
//        {
//            s1 += m + n  + x + '0';
//            x = 0;
//        }
//        --i;
//        --j;
//    }
//    reverse(s1.begin(), s1.end());
//    return s1;
//}
//
//int main()
//{
//    addStrings("11", "123");
//    return 0;
//}

//#include <string>
//
//using namespace std;
//
//class Solution {
//public:
//    string addStrings(string num1, string num2) {
//        int size1 = num1.size(), size2 = num2.size();
//        string s1;
//        s1.reserve(size1 > size2 ? size1 + 1 : size2 + 1);
//        int i = num1.size() - 1, j = num2.size() - 1;
//        int x = 0; // 进位
//        while (i >= 0 || j >= 0) {
//            int m = i >= 0 ? num1[i] - '0' : 0;
//            int n = j >= 0 ? num2[j] - '0' : 0;
//            if (m + n + x >= 10) {
//                s1 += m + n + x - 10 + '0';
//                x = 1;
//            }
//            else {
//                s1 += m + n + x + '0';
//                x = 0;
//            }
//            --i;
//            --j;
//        }
//        if (x == 1)
//            s1 += '1';
//        reverse(s1.begin(), s1.end());
//        return s1;
//    }
//
//    string multiply(string num1, string num2) {
//        int size1 = num1.size();
//        int size2 = num2.size();
//        string s  = "0";
//        s.reserve(size1 + size2);
//
//        for (int i = num2.size() - 1; i >= 0; i--) // 
//        {
//            int x = 0;
//            int m = num2[i] - '0';
//            if (m == 0)
//                continue;
//            for (int j = num1.size() - 1; j >= 0; j--)
//            {
//                int n = num1[j] - '0';
//                x = m * n;
//                string tmp(to_string(x));
//                for (int k = i + j; k < num2.size() - 1 + num1.size() - 1; k++)
//                {
//                    tmp += '0';
//                }
//                s = addStrings(s, tmp);
//            }
//        }
//
//        return s;
//    }
//};
//
//int main()
//{
//    Solution s;
//    s.multiply("9133", "0");
//    return 0;
//}


//#include <iostream>
//#include <assert.h>
//using namespace std;
//
//namespace Lzc
//{
//	template<class T>
//	struct list_node
//	{
//		T _data;
//		list_node<T>* _next;
//		list_node<T>* _prev;
//
//		list_node() = default;
//
//		template <class... Args>
//		list_node(Args&&... args)
//			: _next(nullptr)
//			, _prev(nullptr)
//			, _data(std::forward<Args>(args)...)
//		{
//		}
//	};
//
//	template<class T, class Ref, class Ptr>
//	struct list_iterator
//	{
//		typedef list_node<T> Node;
//		typedef list_iterator<T, Ref, Ptr> Self;
//		Node* _node;
//
//		list_iterator(Node* node)
//			:_node(node)
//		{
//		}
//
//		Ref operator*()
//		{
//			return _node->_data;
//		}
//
//		Ptr operator->()
//		{
//			return &_node->_data;
//		}
//
//		Self& operator++()
//		{
//			_node = _node->_next;
//			return *this;
//		}
//
//		Self& operator--()
//		{
//			_node = _node->_prev;
//			return *this;
//		}
//
//		Self operator++(int)
//		{
//			Self tmp(*this);
//			_node = _node->_next;
//
//			return tmp;
//		}
//
//		Self& operator--(int)
//		{
//			Self tmp(*this);
//			_node = _node->_prev;
//
//			return tmp;
//		}
//
//		bool operator!=(const Self& s) const
//		{
//			return _node != s._node;
//		}
//
//		bool operator==(const Self& s) const
//		{
//			return _node == s._node;
//		}
//	};
//
//	template<class T>
//	class list
//	{
//		typedef list_node<T> Node;
//	public:
//
//		typedef list_iterator<T, T&, T*> iterator;
//		typedef list_iterator<T, const T&, const T*> const_iterator;
//
//		iterator begin()
//		{
//			return _head->_next;
//		}
//
//		iterator end()
//		{
//			return _head;
//		}
//
//		const_iterator begin() const
//		{
//			return _head->_next;
//		}
//
//		const_iterator end() const
//		{
//			return _head;
//		}
//
//		void empty_init()
//		{
//			_head = new Node;
//			_head->_next = _head;
//			_head->_prev = _head;
//			_size = 0;
//		}
//
//		list()
//		{
//			empty_init();
//		}
//
//		list(initializer_list<T> il)
//		{
//			empty_init();
//			for (auto& e : il)
//			{
//				push_back(e);
//			}
//		}
//
//		// lt2(lt1)
//		list(const list<T>& lt)
//		{
//			empty_init();
//
//			for (auto& e : lt)
//			{
//				push_back(e);
//			}
//		}
//
//		// lt1 = lt3
//		list<T>& operator=(list<T> lt)
//		{
//			swap(lt);
//			return *this;
//		}
//
//		~list()
//		{
//			clear();
//			delete _head;
//			_head = nullptr;
//		}
//
//		void clear()
//		{
//			auto it = begin();
//			while (it != end())
//			{
//				it = erase(it);
//			}
//		}
//
//		void swap(list<T>& lt)
//		{
//			std::swap(_head, lt._head);
//			std::swap(_size, lt._size);
//		}
//
//		void push_back(const T& x)
//		{
//			insert(end(), x);
//		}
//
//		void push_back(T&& x)
//		{
//			insert(end(), forward<T>(x));
//		}
//
//		// 万能引用
//		/*template<class X>
//		void push_back(X&& x)
//		{
//			insert(end(), forward<X>(x));
//		}*/
//
//		template <class... Args>
//		void emplace_back(Args&&... args)
//		{
//			insert(end(), std::forward<Args>(args)...);
//		}
//
//		void push_front(const T& x)
//		{
//			insert(begin(), x);
//		}
//
//		iterator insert(iterator pos, const T& x)
//		{
//			Node* cur = pos._node;
//			Node* prev = cur->_prev;
//			Node* newnode = new Node(x);
//
//			// prev newnode cur
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			newnode->_prev = prev;
//			prev->_next = newnode;
//
//			++_size;
//
//			return newnode;
//		}
//
//		iterator insert(iterator pos, T&& x)
//		{
//			Node* cur = pos._node;
//			Node* prev = cur->_prev;
//			Node* newnode = new Node(forward<T>(x));
//
//			// prev newnode cur
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			newnode->_prev = prev;
//			prev->_next = newnode;
//
//			++_size;
//
//			return newnode;
//		}
//
//		//template<class X>
//		//iterator insert(iterator pos, X&& x)
//		//{
//		//	Node* cur = pos._node;
//		//	Node* prev = cur->_prev;
//		//	Node* newnode = new Node(forward<X>(x));
//
//		//	// prev newnode cur
//		//	newnode->_next = cur;
//		//	cur->_prev = newnode;
//		//	newnode->_prev = prev;
//		//	prev->_next = newnode;
//
//		//	++_size;
//
//		//	return newnode;
//		//}
//
//		template <class... Args>
//		iterator insert(iterator pos, Args&&... args)
//		{
//			Node* cur = pos._node;
//			Node* newnode = new Node(std::forward<Args>(args)...);
//			Node* prev = cur->_prev;
//
//			// prev newnode cur
//			prev->_next = newnode;
//			newnode->_prev = prev;
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			return iterator(newnode);
//		}
//
//		void pop_back()
//		{
//			erase(--end());
//		}
//
//		void pop_front()
//		{
//			erase(begin());
//		}
//
//		iterator erase(iterator pos)
//		{
//			assert(pos != end());
//
//			Node* prev = pos._node->_prev;
//			Node* next = pos._node->_next;
//
//			prev->_next = next;
//			next->_prev = prev;
//			delete pos._node;
//
//			--_size;
//
//			return next;
//		}
//
//		size_t size() const
//		{
//			return _size;
//		}
//
//		bool empty() const
//		{
//			return _size == 0;
//		}
//	private:
//		Node* _head;
//		size_t _size;
//	};
//}
//
//int main()
//{
//	string s = "123456";
//	Lzc::list<string> l;
//	l.push_back(s);
//	s = "222";
//	cout << *l.begin() << endl;
//
//	return 0;
//}


//#pragma once
//#include<assert.h>
//
//namespace Lzc
//{
//	template<class T>
//	struct list_node
//	{
//		T _data;
//		list_node<T>* _next;
//		list_node<T>* _prev;
//
//		list_node() = default;
//
//		template <class... Args>
//		list_node(Args&&... args)
//			: _next(nullptr)
//			, _prev(nullptr)
//			, _data(std::forward<Args>(args)...)
//		{
//		}
//	};
//
//	template<class T, class Ref, class Ptr>
//	struct list_iterator
//	{
//		typedef list_node<T> Node;
//		typedef list_iterator<T, Ref, Ptr> Self;
//		Node* _node;
//
//		list_iterator(Node* node)
//			:_node(node)
//		{
//		}
//
//		Ref operator*()
//		{
//			return _node->_data;
//		}
//
//		Ptr operator->()
//		{
//			return &_node->_data;
//		}
//
//		Self& operator++()
//		{
//			_node = _node->_next;
//			return *this;
//		}
//
//		Self& operator--()
//		{
//			_node = _node->_prev;
//			return *this;
//		}
//
//		Self operator++(int)
//		{
//			Self tmp(*this);
//			_node = _node->_next;
//
//			return tmp;
//		}
//
//		Self& operator--(int)
//		{
//			Self tmp(*this);
//			_node = _node->_prev;
//
//			return tmp;
//		}
//
//		bool operator!=(const Self& s) const
//		{
//			return _node != s._node;
//		}
//
//		bool operator==(const Self& s) const
//		{
//			return _node == s._node;
//		}
//	};
//
//	template<class T>
//	class list
//	{
//		typedef list_node<T> Node;
//	public:
//		typedef list_iterator<T, T&, T*> iterator;
//		typedef list_iterator<T, const T&, const T*> const_iterator;
//
//		iterator begin()
//		{
//			return _head->_next;
//		}
//
//		iterator end()
//		{
//			return _head;
//		}
//
//		const_iterator begin() const
//		{
//			return _head->_next;
//		}
//
//		const_iterator end() const
//		{
//			return _head;
//		}
//
//		void empty_init()
//		{
//			_head = new Node;
//			_head->_next = _head;
//			_head->_prev = _head;
//			_size = 0;
//		}
//
//		list()
//		{
//			empty_init();
//		}
//
//		list(initializer_list<T> il)
//		{
//			empty_init();
//			for (auto& e : il)
//			{
//				push_back(e);
//			}
//		}
//
//		// lt2(lt1)
//		list(const list<T>& lt)
//		{
//			empty_init();
//
//			for (auto& e : lt)
//			{
//				push_back(e);
//			}
//		}
//
//		// lt1 = lt3
//		list<T>& operator=(list<T> lt)
//		{
//			swap(lt);
//			return *this;
//		}
//
//		~list()
//		{
//			clear();
//			delete _head;
//			_head = nullptr;
//		}
//
//		void clear()
//		{
//			auto it = begin();
//			while (it != end())
//			{
//				it = erase(it);
//			}
//		}
//
//		void swap(list<T>& lt)
//		{
//			std::swap(_head, lt._head);
//			std::swap(_size, lt._size);
//		}
//
//		void push_back(const T& x)
//		{
//			insert(end(), x);
//		}
//
//		void push_back(T&& x)
//		{
//			insert(end(), forward<T>(x));
//		}
//
//		// 万能引用
//		/*template<class X>
//		void push_back(X&& x)
//		{
//			insert(end(), forward<X>(x));
//		}*/
//
//		template <class... Args>
//		void emplace_back(Args&&... args)
//		{
//			insert(end(), std::forward<Args>(args)...);
//		}
//
//		void push_front(const T& x)
//		{
//			insert(begin(), x);
//		}
//
//		iterator insert(iterator pos, const T& x)
//		{
//			Node* cur = pos._node;
//			Node* prev = cur->_prev;
//			Node* newnode = new Node(x);
//
//			// prev newnode cur
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			newnode->_prev = prev;
//			prev->_next = newnode;
//
//			++_size;
//
//			return newnode;
//		}
//
//		iterator insert(iterator pos, T&& x)
//		{
//			Node* cur = pos._node;
//			Node* prev = cur->_prev;
//			Node* newnode = new Node(forward<T>(x));
//
//			// prev newnode cur
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			newnode->_prev = prev;
//			prev->_next = newnode;
//
//			++_size;
//
//			return newnode;
//		}
//
//
//		// 万能引用
//		//template<class X>
//		//iterator insert(iterator pos, X&& x)
//		//{
//		//	Node* cur = pos._node;
//		//	Node* prev = cur->_prev;
//		//	Node* newnode = new Node(forward<X>(x));
//
//		//	// prev newnode cur
//		//	newnode->_next = cur;
//		//	cur->_prev = newnode;
//		//	newnode->_prev = prev;
//		//	prev->_next = newnode;
//
//		//	++_size;
//
//		//	return newnode;
//		//}
//
//		template <class... Args>
//		iterator insert(iterator pos, Args&&... args)
//		{
//			Node* cur = pos._node;
//			Node* newnode = new Node(std::forward<Args>(args)...);
//			Node* prev = cur->_prev;
//
//			// prev newnode cur
//			prev->_next = newnode;
//			newnode->_prev = prev;
//			newnode->_next = cur;
//			cur->_prev = newnode;
//			return iterator(newnode);
//		}
//
//		void pop_back()
//		{
//			erase(--end());
//		}
//
//		void pop_front()
//		{
//			erase(begin());
//		}
//
//		iterator erase(iterator pos)
//		{
//			assert(pos != end());
//
//			Node* prev = pos._node->_prev;
//			Node* next = pos._node->_next;
//
//			prev->_next = next;
//			next->_prev = prev;
//			delete pos._node;
//
//			--_size;
//
//			return next;
//		}
//
//		size_t size() const
//		{
//			return _size;
//		}
//
//		bool empty() const
//		{
//			return _size == 0;
//		}
//	private:
//		Node* _head;
//		size_t _size;
//	};
//}

#include <iostream>
using namespace std;

double Divide(int a, int b) // noexcept
{
    // 当 b == 0 时抛出异常
    if (b == 0)
    {
        throw "Division by zero condition!";
    }
    return (double)a / (double)b;
}

int main()
{
    try
    {
        int len, time;
        cin >> len >> time;
        cout << Divide(len, time) << endl;
    }
    catch (const char* errmsg)
    {
        cout << errmsg << endl;
    }
    catch (...)
    {
        cout << "Unknown Exception" << endl;
    }

    int i = 0;
    cout << noexcept(Divide(1, 2)) << endl; // 0
    cout << noexcept(Divide(1, 0)) << endl; // 0
    cout << noexcept(++i) << endl; // 1

    return 0;
}